package com.feinno.urcs.group.pd.util;

import org.jboss.netty.buffer.ChannelBuffer;
import org.jboss.netty.buffer.ChannelBufferIndexFinder;
import org.jboss.netty.buffer.ChannelBuffers;

import java.nio.charset.Charset;
import java.util.ArrayList;

/**
 * Created by wuhao on 15-7-9.
 */
public class MultiPartContent extends Content {
    /** 解码类型 */
    private Charset curCharset;
    /** 长度 */
    protected int lengthOfWrap;
    /** 分隔符 */
    protected String boundary;
    /** 包体开始 */
    protected String startBoundary;
    /** 包体间隔 */
    protected String middleBoundary;
    /** 包体结尾 */
    protected String endBoundary;

    /**  boundary区分 **/
    public final static String BOUNDARY = "boundary";
    /** 默认boundary **/
    public final static String DEFAULT_BOUNDARY = "498E61C59F72623F";

    /**
     * parseContentList
     * 解析content列表
     *
     * @param body
     */
    public void parseContentList(byte[] body){

        if (getBoundary() == null) {
            // 单一包体内容
            ChannelBuffer channelBuffer = ChannelBuffers.wrappedBuffer(body);
        } else {
            // 多包体
            final byte[] splitBytes = ("--" + getBoundary()).getBytes(getCharset());
            final int len = splitBytes.length;
            ChannelBuffer bodyBuffer = ChannelBuffers.wrappedBuffer(body);
            while (true) {
                // pos为找到 --boundary的长度
                int pos = bodyBuffer.bytesBefore(new ChannelBufferIndexFinder() {
                    @Override
                    public boolean find(ChannelBuffer buffer, int guessedIndex) {
//                        byte cur = buffer.getByte(guessedIndex);
//                        if ((cur == '-') && (buffer.readableBytes() > len)) {
//                            for (int i = 0; i < len; i++) {
//                                if (splitBytes[i] != buffer.getByte(guessedIndex + i))
//                                    return false;
//                            }
//                            return true;
//                        } else
//                            return false;
                        byte cur = buffer.getByte(guessedIndex);
                        if ((cur == splitBytes[0]) && (buffer.readableBytes() > splitBytes.length)) {
                            for (int i = 1; i < splitBytes.length; i++) {
                                if (splitBytes[i] != buffer.getByte(guessedIndex + i))
                                    return false;
                            }
                            return true;
                        } else
                            return false;


                    }
                });
                if (pos == -1) {
                    return;
                }
                if (pos != 0) {
                    if(contentList == null){
                        contentList = new ArrayList<Content>();
                    }
                    // pos -/r/n长度,为content的包体长度
                    ChannelBuffer chipBuffer = bodyBuffer.readBytes(pos - lengthOfWrap);
                    MultiPartContent multiPartContent = new MultiPartContent();
                    contentList.add(multiPartContent);
                    parseContent(chipBuffer, multiPartContent);
                }

                // 空读/r/n--boundary
                bodyBuffer.skipBytes(len + lengthOfWrap);
            }
        }

    }

    /**
     * parseContent
     * 解析content内容
     *
     * @param chipBuffer
     * @return
     */
    protected Content parseContent(ChannelBuffer chipBuffer, MultiPartContent multiPartContent){
        String childBoundary = null;
        String headerLine;

        if (!chipBuffer.readable()) {
            return null;
        }
        // remove leading space characters
        while (chipBuffer.readable() && chipBuffer.getByte(chipBuffer.readerIndex()) <= 0x20) {
            chipBuffer.skipBytes(1);
        }
        if (!chipBuffer.readable()) {
            return null;
        }

        try {
            while ((headerLine = getLine(chipBuffer)) != null) {
                if (headerLine.length() == 1) {// 这是一个回车换行 空白行,表示header已经读完.
                    break;
                }
                multiPartContent.addHeader(headerLine);
                if(childBoundary == null){
                    childBoundary = getChildBoundary(headerLine);
                }
                System.out.print(headerLine);
            }
        } catch (Exception e) {
            return null;
        }

        byte[] chipBody = new byte[chipBuffer.readableBytes()];
        chipBuffer.readBytes(chipBody);
        if(childBoundary != null){
            multiPartContent.setBoundary(childBoundary);
            multiPartContent.parseContentList(chipBody);
        }else {
            multiPartContent.setContent(chipBody);

            System.out.println("/-----------------------------------------\\");
            System.out.println(new String(chipBody));
            System.out.println("\\-----------------------------------------/");
        }
        return null;
    }

    protected String getLine(ChannelBuffer msgBuffer) {
        // a string line may end with \r\n or just \n. so...
        int lineEndPosition = msgBuffer.bytesBefore(ChannelBufferIndexFinder.LF);
        if (lineEndPosition == -1)
            return null;
        String line;
        if(msgBuffer.getByte(msgBuffer.readerIndex()+lineEndPosition-1)=='\r') {
            msgBuffer.setByte(msgBuffer.readerIndex()+lineEndPosition-1, '\n');
            line = msgBuffer.toString(msgBuffer.readerIndex(), lineEndPosition, getCharset());
            lineEndPosition++; // skip  last '\n'
        }
        else {		// only \n exist.
            lineEndPosition++; // skip '\n'
            line = msgBuffer.toString(msgBuffer.readerIndex(), lineEndPosition, getCharset());
        }
        msgBuffer.skipBytes(lineEndPosition);
        return line;
    }

    protected String getChildBoundary(String headerLine){
        String boundary = null;
        //存在boundary
        int boundaryIndex = headerLine.indexOf("boundary");
        if(boundaryIndex > 0){
            boundary = headerLine.substring(boundaryIndex + 10, headerLine.length() - 2);
        }
        return boundary;
    }

    public void setCharset(String c) {
        this.curCharset = c != null ? Charset.forName(c) : Charset.defaultCharset();
        // 定义一些特定字符串信息
        lengthOfWrap = "\r\n".getBytes(getCharset()).length - 1;
    }
    public void setBoundary(String boundary) {
        this.boundary = boundary;
        if (this.boundary == null) {
            //this.boundary = BOUNDARY;
            return;
        }
        getStartBoundary();
        getMiddleBoundary();
        getEndBoundary();
    }

    protected Charset getCharset() {
        if (this.curCharset == null) {
            curCharset = Charset.defaultCharset();
        }
        return this.curCharset;
    }


    protected String getBoundary() {
        if(this.boundary ==null){
            this.boundary = DEFAULT_BOUNDARY;
        }
        return this.boundary;
    }

    protected Charset getCurCharset() {
        return curCharset;
    }

    protected int getLengthOfWrap() {
        return lengthOfWrap;
    }

    protected String getStartBoundary() {
        if (startBoundary == null || startBoundary.length() == 0) {
            startBoundary = "--" + boundary + "\r\n";
        }
        return startBoundary;
    }

    protected String getMiddleBoundary() {
        if (middleBoundary == null || middleBoundary.length() == 0) {
            middleBoundary = "\r\n--" + boundary + "\r\n";
        }
        return middleBoundary;
    }

    protected String getEndBoundary() {
        if (endBoundary == null || endBoundary.length() == 0) {
            endBoundary = "\r\n--" + boundary + "--\r\n";
        }
        return endBoundary;
    }
}
